#include <cstdio>
#include <stack>

using namespace std;

const int Limit_Size = 10000 + 10;
const int Data_Size = 100 + 10;

struct Node
{
    int x, y, time;
};

struct Queue
{
    Node l[ 50000 ];
    int head, tail;
    bool empty( );
    void push( Node );
    void pop( );
    Node front( );
    void init( );
};

int N, M, pi[ Limit_Size ];
bool visit[ Data_Size ][ Data_Size ];
char data[ Data_Size ][ Data_Size ];
Queue q;
stack<int> s;

bool Queue::empty( )
{
    return head > tail;
}

void Queue::push( Node p )
{
    l[ ++tail ] = p;
}

void Queue::pop( )
{
    head++;
}

Node Queue::front( )
{
    return l[ head ];
}

void Queue::init( )
{
    head = 1;
    tail = 0;
}

void init( )
{
    int i, j;
    q.init( );
    for ( i = 0; i < N; i++ )
        scanf("%s", data[ i ]);
    for ( i = 0; i < N; i++ )
        for ( j = 0; j < M; j++ )
        {
            pi[ i * M + j ] = -1;
            if ( data[ i ][ j ] != 'X' )
                visit[ i ][ j ] = true;
            else
                visit[ i ][ j ] = false;
        }
}

void pushVertex( Node t, int x, int y )
{
    visit[ x ][ y ] = false;
    pi[ x * M + y ] = t.x * M + t.y;
    t.x = x; t.y = y;
    if ( data[ x ][ y ] == '.' )
        t.time = 1;
    else
        t.time = data[ x ][ y ] - '0' + 1;
    q.push( t );
}

void bfs( )
{
    while ( !q.empty( ) )
        q.pop( );
    Node t;
    int co = 0;
    t.x = 0; t.y = 0; t.time = 1;
    q.push( t );
    visit[ 0 ][ 0 ] = false;
    while ( !q.empty( ) )
    {
        t = q.front( );
        if ( t.x == N - 1 && t.y == M - 1 && t.time == 1 )
            break;
        q.pop( );
        if ( t.time != 1 )
        {
            t.time--;
            q.push( t );
        }
        else
        {
            if ( t.x != 0 )
                if ( visit[ t.x - 1 ][ t.y ] )
                    pushVertex( t, t.x - 1, t.y );
            if ( t.y != 0 )
                if ( visit[ t.x ][ t.y - 1 ] )
                    pushVertex( t, t.x, t.y - 1 );
            if ( t.x != N - 1 )
                if ( visit[ t.x + 1 ][ t.y ] )
                    pushVertex( t, t.x + 1, t.y );
            if ( t.y != M - 1 )
                if ( visit[ t.x ][ t.y + 1 ] )
                    pushVertex( t, t.x, t.y + 1 );
        }
    }
}

void print( )
{
    if ( !visit[ N - 1 ][ M - 1 ] )
    {
        while ( !s.empty( ) )
            s.pop( );
        int Min_Time = -1, t = N * M - 1, c = 1, p, a, b, i;
        while ( t != -1 )
        {
            if ( data[ t / M ][ t % M ] == '.' )
                Min_Time++;
            else
                Min_Time += data[ t / M ][ t % M ] - '0' + 1;
            s.push( t );
            t = pi[ t ];
        }
        printf("It takes %d seconds to reach the target position, let me show you the way.\n", Min_Time);
        while ( c <= Min_Time )
        {
            t = s.top( );
            s.pop( );
            p = s.top( );
            a = p / M; b = p % M;
            printf("%ds:(%d,%d)->(%d,%d)\n", c, t / M, t % M, a, b);
            for ( i = 0; i < data[ a ][ b ] - '0'; i++ )
            {
                c++;
                printf("%ds:FIGHT AT (%d,%d)\n", c, a, b);
            }
            c++;
        }
    }
    else
        printf("God please help our poor hero.\n");
    printf("FINISH\n");
}

int main( )
{
    //freopen("1026.in", "r", stdin);
    //freopen("1026.out1", "w", stdout);
    while ( scanf("%d%d", &N, &M) != EOF )
    {
        init( );
        bfs( );
        print( );
    }
    return 0;
}

